package com.faithbj.printer;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Arrays;

import org.apache.commons.logging.Log;
import org.openqa.selenium.TimeoutException;
import org.springframework.stereotype.Component;

import com.faithbj.printer.logger.Logger;

@Component("exceptionProxy")
public class ExceptionProxy {

	@Logger
	private Log log;

	public static final int RETRY = 3;

	/**
	 * 异常代理
	 * @param o 要代理的类实例
	 * @param methodName 要代理的方法
	 * @param parameterTypes 要代理方法的类型
	 * @param args 要代理方法的参数
	 * @return
	 */
	public boolean exceptionHandler(Object o, String methodName,
			Class<?>[] parameterTypes, Object[] args) {
		boolean isSuccess = false;
		try {
			Method method = o.getClass().getMethod(methodName, parameterTypes);
			method.invoke(o, args);
			isSuccess = true;
		} catch (NoSuchMethodException | SecurityException
				| IllegalAccessException | IllegalArgumentException e) {
			e.printStackTrace();
			log.error(e);
			log.error("方法调用异常: class--" + o.getClass().getName()
					+ " ; methodName--" + methodName);
		} catch (InvocationTargetException e) {
			log.error(e.getCause());
			log.error(Arrays.asList(e.getStackTrace()));
		}
		return isSuccess;
	}

	//back
	public boolean exceptionHandlerBak(Object o, String methodName,
			Class<?>[] parameterTypes, Object[] args) {
		boolean isSuccess = false;
		int cnt = 0;
		while (!isSuccess && cnt < ExceptionProxy.RETRY) {
			try {
				Method method = o.getClass().getMethod(methodName,
						parameterTypes);
				method.invoke(o, args);
				isSuccess = true;
			} catch (NoSuchMethodException | SecurityException
					| IllegalAccessException | IllegalArgumentException e) {
				e.printStackTrace();
				log.error(e);
				log.error("方法调用异常: class--" + o.getClass().getName()
						+ " ; methodName--" + methodName);
				break;
			} catch (InvocationTargetException e) {
				log.error(e.getCause());
				log.error(Arrays.asList(e.getStackTrace()));
				break;
			} catch (TimeoutException e) {
				e.printStackTrace();
				log.error(e);
				log.warn("超时异常： class--" + o.getClass().getName()
						+ " ; methodName--" + methodName);
				cnt++;
				log.info("超时重试：第 " + cnt + " 次");
			} catch (Exception e) {
				e.printStackTrace();
				log.error(e);
				log.error("method failure: " + methodName);
				break;
			}
		}
		return isSuccess;
	}

}
